	//
	//  History.swift
	//  hello
	//
	//  Created by 赵康 on 2024/11/11.
	//

import Fluent
import Vapor
import Logging

// 添加向下兼容的日期格式化辅助函数
private func formatDate(_ date: Date) -> String {
	let formatter = DateFormatter()
	formatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss'Z'"
	formatter.timeZone = TimeZone(secondsFromGMT: 0)
	return formatter.string(from: date)
}

final class History: Model, Content, @unchecked Sendable {
	static var schema: String { SchemaEnum.histories.rawValue}
	
	@ID(key: .id)
	var id: UUID?
	
	@Parent(key: FieldKeys.user)
	var user: User
	
	@Parent(key: FieldKeys.audio)
	var audio: Audio
	
	@Field(key: FieldKeys.progress)
	var progress: Double // 听力进度
	
	@Field(key: FieldKeys.duration)
	var duration: Double
	
	@Field(key: FieldKeys.isFinished)
	var isFinished: Bool // 是否听完
	
	@Field(key: FieldKeys.lastListenedAt)
	var lastListenedAt: Date?
	
	@Timestamp(key: FieldKeys.createdAt, on: .create)
	var createdAt: Date?
	
	@Field(key: FieldKeys.deleteStatus)
	var deleteStatus: DeleteStatus
	
	@Field(key: FieldKeys.deletedAt)
	var deletedAt: Date?
	
	@Field(key: FieldKeys.listenedDuration)
	var listenedDuration: Double // 已听时长
	
	@Field(key: FieldKeys.listenStatus)
	var listenStatus: ListenStatus
	
	@Field(key: FieldKeys.completedCount)
	var completedCount: Int // 完成次数
	
	init() { }
	
	init(
		id: UUID? = nil,
		userID: User.IDValue,
		audioID: Audio.IDValue,
		progress: Double,
		duration: Double,
		isFinished: Bool,
		lastListenedAt: Date?,
		createdAt: Date?,
		listenedDuration: Double,
		listenStatus: ListenStatus = .inProgress,  // 添加这个参数
		completedCount: Int = 0                    // 添加这个参数
	) {
		self.id = id
		self.$user.id = userID
		self.$audio.id = audioID
		self.progress = progress
		self.duration = duration
		self.isFinished = isFinished
		self.lastListenedAt = lastListenedAt
		self.createdAt = createdAt
		self.listenedDuration = listenedDuration
		self.deleteStatus = .normal
		self.deletedAt = nil
		self.listenStatus = listenStatus          // 初始化这个字段
		self.completedCount = completedCount      // 初始化这个字段
	}
}

extension History {
  static func getCheckInStats(for userID: UUID, year: Int, month: Int, db: Database) async throws -> MonthlyCheckInResponse {
    let logger = Logger(label: "History.getCheckInStats")
    logger.info("开始获取用户 \(userID) 的打卡统计, 年: \(year), 月: \(month)")
    
    // 获取指定月份的时间范围
    let calendar = Calendar.mondayFirst
    let dateComponents = DateComponents(year: year, month: month)
    guard let startDate = calendar.date(from: dateComponents),
          let endDate = calendar.date(byAdding: .month, value: 1, to: startDate) else {
      logger.error("日期计算错误")
      throw Abort(.badRequest, reason: "Invalid date")
    }
    
    logger.info("月份时间范围: 开始=\(formatDate(startDate)), 结束=\(formatDate(endDate))")
    
    // 获取用户的每日学习目标
    guard let user = try await User.find(userID, on: db) else {
      logger.error("找不到用户: \(userID)")
      throw Abort(.notFound, reason: "User not found")
    }
    
    logger.info("用户每日目标: \(user.dailyGoal)秒")
    
    // 查询该月份的所有历史记录
    let histories = try await History.query(on: db)
      .filter(\.$user.$id == userID)
      .filter(\.$lastListenedAt >= startDate)
      .filter(\.$lastListenedAt < endDate)
      .all()
    
    logger.info("查询到 \(month) 月历史记录: \(histories.count) 条")
    
    // 按日期分组,计算每天的总听力时长
    var dailyListeningTime: [Date: Double] = [:]
    
    for history in histories {
      guard let date = history.lastListenedAt else { continue }
      let dayStart = calendar.startOfDay(for: date)
      let currentTotal = dailyListeningTime[dayStart] ?? 0
      dailyListeningTime[dayStart] = currentTotal + history.listenedDuration
      
      logger.info("用户 \(userID) 在 \(formatDate(dayStart)) 的累计听力时长: \(dailyListeningTime[dayStart]!)秒, 历史记录ID: \(history.id?.uuidString ?? "nil"), 时长: \(history.listenedDuration)秒")
    }
    
    // 筛选出达到每日目标的日期作为有效打卡日期
    let checkInDates = dailyListeningTime.filter { $0.value >= user.dailyGoal }
                                        .keys
                                        .sorted()
    
    logger.info("本月达到目标的天数: \(checkInDates.count)")
    
    // 获取所有历史打卡记录（不受月份限制）
    let allHistories = try await History.query(on: db)
      .filter(\.$user.$id == userID)
      .all()
    
    logger.info("查询到所有时间的历史记录: \(allHistories.count) 条")
    
    // 计算所有时间的打卡天数
    var allTimeDailyListeningTime: [Date: Double] = [:]
    
    for history in allHistories {
      guard let date = history.lastListenedAt else { continue }
      let dayStart = calendar.startOfDay(for: date)
      let currentTotal = allTimeDailyListeningTime[dayStart] ?? 0
      allTimeDailyListeningTime[dayStart] = currentTotal + history.listenedDuration
    }
    
    // 筛选出所有时间内达到每日目标的日期
    let allCheckInDates = allTimeDailyListeningTime.filter { $0.value >= user.dailyGoal }
                                               .keys
                                               .count
    
    logger.info("所有时间达到目标的天数: \(allCheckInDates), 用户记录的总打卡天数: \(user.totalCheckIns)")
    
    // 确保用户的totalCheckIns和实际打卡数量一致
    if user.totalCheckIns != allCheckInDates {
      logger.info("更新用户总打卡天数: \(user.totalCheckIns) -> \(allCheckInDates)")
      user.totalCheckIns = allCheckInDates
      try await user.save(on: db)
    }
    
    return MonthlyCheckInResponse(
      stats: CheckInStats(
        currentStreak: user.currentStreak,
        totalCheckIns: checkInDates.count,
        totalAllTimeCheckIns: allCheckInDates,
        checkInDates: checkInDates
      ),
      year: year,
      month: month
    )
  }
}

struct CheckInStats: Content {
  let currentStreak: Int // 当前连续打卡天数
  let totalCheckIns: Int // 总打卡天数（指定月份）
  let totalAllTimeCheckIns: Int // 总打卡天数（所有月份）
  let checkInDates: [Date] // 打卡日期列表
}

struct MonthlyCheckInResponse: Content {
  let stats: CheckInStats
  let year: Int
  let month: Int
}

struct UpdateHistoryProgress: Content {
	var progress: Double
	var listenedDuration: Double
}
enum DeleteStatus: Int, Codable {
	case normal = 0
	case softDeleted = 1
}
enum ListenStatus: Int, Codable {
	case inProgress = 0 // 正在听
	case completed = 1 // 听完了
	case relistening = 2 // 重新听
}

struct HistoryResponse: Content {
	let id: UUID?
	let progress: Double
	let duration: Double
	let isFinished: Bool
	let lastListenedAt: Date?
	let createdAt: Date?
	let listenedDuration: Double
	let deleteStatus: DeleteStatus
	let deletedAt: Date?
	let listenStatus: ListenStatus
	let completedCount: Int
		// 音频基本信息，与 SearchAudioResponse 保持一致的结构
	let audio: AudioSearchResponse
}
struct FetchHistoriesRequest: Content {
	var timeRange: HistoryTimeRange?
	var searchText: String?
	var groupBy: HistoryGroupBy?
	var page: Int = 1
	var per: Int = 20
}
struct HistoryGroupByAlbumResponse: Content {
	let albumID: UUID
	let albumTitle: String
	let albumCover: String?
	let histories: [HistoryResponse]
}
struct BatchDeleteHistoriesRequest: Content {
	var historyIDs: [UUID]
	var deleteAll: Bool?
	var albumID: UUID?
}
struct RestoreHistoriesRequest: Content {
	var historyIDs: [UUID]
	var restoreAll: Bool?
	var albumID: UUID?
}

  // 添加响应结构体
struct AudioCountResponse: Content {
  let totalListened: Int  // 用户听过的音频总数
  let totalCompleted: Int // 用户已完成的音频数量
  let todayListened: Int // 用户今天听了多少个音频
}

struct RecentCoverResponse: Content {
  let id: UUID
  let audioID: UUID
  let audioCover: String  // 非可选类型
  let albumID: UUID
  let albumCover: String  // 非可选类型
  let lastListenedAt: Date  // 非可选类型
}
